/*
*
* ████████╗░█████╗░███████╗██████╗░░█████╗░
* ╚══██╔══╝██╔══██╗██╔════╝██╔══██╗██╔══██╗
* ░░░██║░░░██║░░██║█████╗░░██████╦╝███████║
* ░░░██║░░░██║░░██║██╔══╝░░██╔══██╗██╔══██║
* ░░░██║░░░╚█████╔╝██║░░░░░██████╦╝██║░░██║
* ░░░╚═╝░░░░╚════╝░╚═╝░░░░░╚═════╝░╚═╝░░╚═╝
* 
*  :: 九方通逊-Henry ::   Copyright©2020 tofba.com  
* 
*/
package com.lmexpress.service.impl;

import java.io.File;
import java.net.URL;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import org.apache.commons.collections.CollectionUtils;
import org.apache.commons.io.FileUtils;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import com.google.gson.Gson;
import com.google.gson.GsonBuilder;
import com.google.gson.reflect.TypeToken;
import com.lmexpress.enums.ApiCredential;
import com.lmexpress.enums.ApiOrderError;
import com.lmexpress.enums.LabelFormat;
import com.lmexpress.enums.LabelSuffix;
import com.lmexpress.orm.openapi.ExpressOrderApi;
import com.lmexpress.orm.openapi.OrderInvoice;
import com.lmexpress.orm.rest.ApiLabelResponse;
import com.lmexpress.orm.rest.ApiOrderResponse;
import com.lmexpress.orm.vemmis.VmmisInvoice;
import com.lmexpress.orm.vemmis.VmmisOrder;
import com.lmexpress.orm.vemmis.VmmisParam;
import com.lmexpress.service.ApiService;
import com.lmexpress.util.ApiUtil;
import com.lmexpress.util.HttpClientPoolUtil;
import com.lmexpress.util.HttpClientResult;

/**
 * 
 * <纽门ERP.>
 * 
 * @author Henry(fba02)
 * @version [版本号, 2020-12-09]
 * @see [相关类/方法]
 * @since [产品/模块版本]
 */
public class VmmisClient implements ApiService {
	private Logger LOGGER = LoggerFactory.getLogger(VmmisClient.class);
	private final static Integer OK = 1;

	@Override
	public ApiOrderResponse preProcessCreateOrder(ExpressOrderApi expressOrderApi) {
		// String countryCode = expressOrderApi.getCountryCode();
		// String consigneeState = expressOrderApi.getConsigneeState();
		// return new ApiOrderResponse(false, null,
		// PropertiesUtil.getProperty("k5.usps.mail.only.support.us"), false, null);
		return null;
	}

	@Override
	public String mapping(ExpressOrderApi expressOrderApi) {
		Map<String, String> apiCredentials = expressOrderApi.getApiCredentials();
		String customerId = apiCredentials.get(ApiCredential.VMMIS_CUSTOMER_ID.getKey());// 客户ID
		String key = apiCredentials.get(ApiCredential.VMMIS_KEY.getKey());// 纽门秘钥
		// String url = pipeline.get(ApiConfigure.VMMIS_SERVER_URL.getKey());// 接口地址
		long timeStamp = System.currentTimeMillis();
		// String res = HttpClientPoolUtil.sendGet(url +
		// "/cgi-bin/EmsData.dll?DoApp&{\"RequestName\":\"TimeStamp\"}");
		// date = ApiUtil.subNumFromStr(res);
		String orgin = String.valueOf(customerId) + timeStamp + key;
		String md5 = ApiUtil.Md5(orgin);
		VmmisParam vimParam = new VmmisParam();
		vimParam.setRequestName("PreInputSet");
		vimParam.setIcID(customerId);
		vimParam.setMD5(md5);
		vimParam.setTimeStamp(timeStamp);
		VmmisOrder vmmisOrder = new VmmisOrder();
		vmmisOrder.setcNum(expressOrderApi.getCustomerInvoiceCode());
		vmmisOrder.setcEmsKind(apiCredentials.get(ApiCredential.VMMIS_PRODUCT_NAME.getKey()));
		vmmisOrder.setcDes(expressOrderApi.getCountryCode());
		vmmisOrder.setcRCountry(expressOrderApi.getShipperCountry());
		if (null != expressOrderApi.getWeight()) {
			vmmisOrder.setfWeight(String.valueOf(expressOrderApi.getWeight()));
		}
		vmmisOrder.setcReceiver(expressOrderApi.getConsigneeName());
		vmmisOrder.setcRUnit(expressOrderApi.getConsigneeCompanyName());
		vmmisOrder.setcRAddr(expressOrderApi.getConsigneeAddress());
		vmmisOrder.setcRCity(expressOrderApi.getConsigneeCity());
		vmmisOrder.setcRPostcode(expressOrderApi.getConsigneePostCode());
		vmmisOrder.setcRProvince(expressOrderApi.getConsigneeState());
		vmmisOrder.setcRCountry(expressOrderApi.getCountryCode());
		String mobile = expressOrderApi.getConsigneeMobile();
		String phone = expressOrderApi.getConsigneeTelephone();
		vmmisOrder.setcRPhone(StringUtils.isBlank(phone) ? mobile : phone);
		vmmisOrder.setcREmail(expressOrderApi.getConsigneeEmail());
		vmmisOrder.setcRSms(StringUtils.isBlank(mobile) ? phone : mobile);
		vmmisOrder.setiQuantity(expressOrderApi.getOrderPiece() == null ? "1" : expressOrderApi.getOrderPiece().toString());
		vmmisOrder.setcMoney(StringUtils.isBlank(expressOrderApi.getCurrencyCode()) ? DEFAULT_CURRENCY : expressOrderApi.getCurrencyCode());
		List<VmmisInvoice> vmmisInvoices = new ArrayList<VmmisInvoice>();
		List<OrderInvoice> orderInvoices = expressOrderApi.getOrderInvoices();
		VmmisInvoice vmmisInvoice = null;
		if (CollectionUtils.isNotEmpty(orderInvoices)) {
			for (OrderInvoice orderInvoice : orderInvoices) {
				vmmisInvoice = new VmmisInvoice();
				vmmisInvoice.setCxGoods(orderInvoice.getSkuNameCn());
				vmmisInvoice.setIxQuantity(orderInvoice.getInvoicePcs() == null ? "1" : orderInvoice.getInvoicePcs().toString());
				if (null != orderInvoice.getInvoiceAmount()) {
					vmmisInvoice.setFxPrice(orderInvoice.getInvoiceAmount().toString());
				}
				vmmisInvoice.setCxGoodsA(orderInvoice.getSkuNameEn());
				vmmisInvoice.setCxGCodeA(orderInvoice.getHsCode());
				vmmisInvoice.setCxGCodeC(orderInvoice.getSkuCode());
				vmmisInvoices.add(vmmisInvoice);
			}
			vmmisOrder.setGoodsList(vmmisInvoices);
		}
		List<VmmisOrder> vmmisOrders = new ArrayList<VmmisOrder>();
		vmmisOrders.add(vmmisOrder);
		vimParam.setRecList(vmmisOrders);
		GsonBuilder gsonBuilder = new GsonBuilder();
		Gson gson = gsonBuilder.disableHtmlEscaping().create();
		String orderJson = gson.toJson(vimParam);
		if (StringUtils.isNotBlank(orderJson)) {
			orderJson = orderJson.replace("\r\n", " ");
			orderJson = orderJson.replace("\r", " ");
			orderJson = orderJson.replace("\n", " ");
			orderJson = orderJson.replace("&", " ");
		}
		return orderJson;
	}

	@SuppressWarnings("unchecked")
	@Override
	public ApiOrderResponse createOrder(ExpressOrderApi expressOrderApi) {
		ApiOrderResponse apiOrderResponse = preProcessCreateOrder(expressOrderApi);
		if (null != apiOrderResponse) {
			return apiOrderResponse;
		}
		String orderJson = mapping(expressOrderApi);
		Map<String, String> apiCredentials = expressOrderApi.getApiCredentials();
		try {
			HttpClientResult httpClientResult = HttpClientPoolUtil.doPost(apiCredentials.get(ApiCredential.VMMIS_SERVER_URL.getKey()) + "/cgi-bin/EmsData.dll?DoApp", null, orderJson);
			LOGGER.info("vmmis.shipment.request:{}", orderJson);
			if (null == httpClientResult) {
				return new ApiOrderResponse(false, null, ApiOrderError.SERVICE_NO_DATA_RETURN.getMessage(), true, null);
			}
			String response = httpClientResult.getContent();
			if (StringUtils.isBlank(response)) {
				return new ApiOrderResponse(false, null, ApiOrderError.SERVICE_NO_DATA_RETURN.getMessage(), true, null);
			}
			LOGGER.info("vmmis.shipment.response:{}", response);
			Map<String, Object> responseMap = new Gson().fromJson(response, new TypeToken<Map<String, Object>>() {
			}.getType());
			List<Map<String, Object>> errList = (List<Map<String, Object>>) responseMap.get("ErrList");
			if (OK.equals(Double.valueOf(responseMap.get("OK").toString()).intValue())) {
				String trackNumber = (String) errList.get(0).get("cNo");
				String url = (String) errList.get(0).get("cBy5");
				String thirdPartyorderNo = String.valueOf(errList.get(0).get("iID"));
				// iID
				String pdfName = trackNumber + LabelSuffix.PDF.getSuffix();
				// 当前月份
				String centrePath = ApiUtil.getCurrentDay() + "/";
				String relativePath = DEFAULT_LABEL_FOLDER + "/" + centrePath;
				String folderPath = DEFAULT_LABEL_ROOT + relativePath;
				if (!new File(folderPath).exists()) {
					new File(folderPath).mkdirs();
				}
				String fileUrl = folderPath + pdfName;
				apiOrderResponse = new ApiOrderResponse();// 回传数据
				try {
					FileUtils.copyURLToFile(new URL(url), new File(fileUrl));
					apiOrderResponse.setLmLabelUrl(relativePath + pdfName);// 本地地址
				} catch (Exception e) {
					LOGGER.error("vmmis.copy.url.to.file.exception", e);
				}
				apiOrderResponse.setSuccess(true);// 成功
				apiOrderResponse.setReferenceNo(expressOrderApi.getCustomerInvoiceCode());
				apiOrderResponse.setTrackNumber(trackNumber);// 追踪号
				apiOrderResponse.setThirdPartyorderNo(thirdPartyorderNo);// LabelId
				apiOrderResponse.setLabelUrl(url);// 远端地址
				apiOrderResponse.setOriginalResponse(response);// 原始参数
				return apiOrderResponse;
			}
			return new ApiOrderResponse(false, null, errList.get(0).get("cMess").toString(), response);
		} catch (Exception e) {
			LOGGER.error("vmmis.shipmet.exception", e);
			return new ApiOrderResponse(false, null, ApiOrderError.CREATE_ORDER_EXCEPTION.getMessage(), false, e.getMessage());
		}
	}

	@Override
	public ApiLabelResponse label(String trackNumber, Map<String, String> pipeline) {
		String customerId = pipeline.get(ApiCredential.VMMIS_CUSTOMER_ID.getKey());// 客户ID
		String key = pipeline.get(ApiCredential.VMMIS_KEY.getKey());// 纽门秘钥
		long date = System.currentTimeMillis();
		String orgin = String.valueOf(customerId) + date + key;
		String MD5 = ApiUtil.Md5(orgin);
		VmmisParam vimParam = new VmmisParam();
		vimParam.setRequestName("sGetLabel");
		vimParam.setIcID(customerId);
		vimParam.setMD5(MD5);
		vimParam.setTimeStamp(date);
		vimParam.setcModelName(pipeline.get(ApiCredential.VMMIS_CMODEL_NAME.getKey()));
		GsonBuilder gsonBuilder = new GsonBuilder();
		Gson gson = gsonBuilder.disableHtmlEscaping().create();
		String json = gson.toJson(vimParam);
		json = json.replace("}", ",\"aNo\":[\"" + trackNumber + "\"]}");
		String downloadLabelUrl = pipeline.get(ApiCredential.VMMIS_SERVER_URL.getKey()) + "/cgi-bin/GInfo.dll?DoApi" + "&" + json;
		String pdfName = trackNumber + LabelSuffix.PDF.getSuffix();
		String centrePath = ApiUtil.getCurrentDay() + File.separator;
		String relativePath = DEFAULT_LABEL_FOLDER + File.separator + centrePath;
		String folderPath = DEFAULT_LABEL_ROOT + relativePath;
		if (!new File(folderPath).exists()) {
			new File(folderPath).mkdirs();
		}
		String fileUrl = folderPath + pdfName;
		ApiLabelResponse apiLabelResponse = new ApiLabelResponse();
		try {
			FileUtils.copyURLToFile(new URL(downloadLabelUrl), new File(fileUrl));
		} catch (Exception e) {
			LOGGER.error("vmmis.copy.url.to.file.exception", e);
		}
		apiLabelResponse.setBarCode(trackNumber);
		apiLabelResponse.setLabelPath(null);
		apiLabelResponse.setLabelFormat(LabelFormat.PDF.getFormat());
		return apiLabelResponse;
	}

	@Override
	public ApiLabelResponse label(String referenceNo, String trackNumber, Map<String, String> configure) {
		return null;
	}

	@Override
	public ApiLabelResponse labelRender(String trackNumber, ExpressOrderApi expressOrderApi) {
		return null;
	}

	@Override
	public void tracking(String trackNumber, Map<String, String> configure) {

	}

	@Override
	public String trackNumber(String code, Map<String, String> configure) {
		return null;
	}

	public static void main(String[] args) throws Exception {
		// ApiService apiService = new VmmisClient();
		ExpressOrderApi expressOrderApi = new ExpressOrderApi();
		Map<String, String> pipeline = new HashMap<String, String>();
		pipeline.put(ApiCredential.VMMIS_SERVER_URL.getKey(), "http://121.201.110.133:8089");
		pipeline.put(ApiCredential.VMMIS_CUSTOMER_ID.getKey(), "711");
		pipeline.put(ApiCredential.VMMIS_KEY.getKey(), "VW7af8rkXKVOhwp");
		pipeline.put(ApiCredential.VMMIS_PRODUCT_NAME.getKey(), "广西EUB线下普");
		pipeline.put(ApiCredential.VMMIS_CMODEL_NAME.getKey(), "FILE_STORE_PDF");

		expressOrderApi.setApiCredentials(pipeline);
		expressOrderApi.setCustomerInvoiceCode("TOFBA4017327");
		expressOrderApi.setCountryCode("AT");
		expressOrderApi.setConsigneeName("franz dertnig");
		expressOrderApi.setConsigneeCompanyName("LM ltd");
		expressOrderApi.setConsigneeAddress("Obere-Marktstraße 12 Top 2");
		expressOrderApi.setConsigneeState("Altenmarkt");
		expressOrderApi.setConsigneeCity("Altenmarkt");
		expressOrderApi.setConsigneeTelephone("4306605081279");
		expressOrderApi.setConsigneePostCode("5541");
		expressOrderApi.setConsigneeEmail("dertnigs@cablelink.at");
		expressOrderApi.setWeight(0.02);
		OrderInvoice orderInvoice = new OrderInvoice();
		orderInvoice.setSkuNameEn("dertnigs@cablelink.at");
		orderInvoice.setSkuNameCn("日用品");
		orderInvoice.setSkuCode("CA0168-3");
		orderInvoice.setInvoiceWeight(0.02);
		orderInvoice.setInvoicePcs(1);
		orderInvoice.setInvoiceAmount(7D);

		List<OrderInvoice> orderInvoices = new ArrayList<OrderInvoice>();
		orderInvoices.add(orderInvoice);
		expressOrderApi.setOrderInvoices(orderInvoices);

		// System.out.println(new
		// Gson().toJson(apiService.createOrder(expressOrderApi)));
		// apiService.label("LZ406349501CN", pipeline);
		System.err.println(ApiCredential.VMMIS_LABEL_TYPE.getReadonly());
		System.err.println(ApiCredential.VMMIS_CUSTOMER_ID.getReadonly());
		//
//        String orderJson = apiService.mapping(expressOrderApi);
//        HttpClientResult httpClientResult = HttpClientPoolUtil.doPost(pipeline.get(ApiConfigure.VMMIS_SERVER_URL.getKey()) + "/cgi-bin/EmsData.dll?DoApp", null, orderJson);
//        System.out.println(httpClientResult.getContent());
//        {
//            "ReturnValue": 1,
//            "OK": 1,
//            "ErrList": [{
//                "iIndex": 0,
//                "iID": 13325990,
//                "bRecInput": false,
//                "cNum": "TOFBA4017320",
//                "cNo": "LZ406349501CN",
//                "cRNo": "",
//                "cCNo": "TOFBA4017320",
//                "cMess": "",
//                "cEmsKinda": "广西EUB线下普",
//                "cReserve": "",
//                "cBy1": "",
//                "cBy2": "",
//                "cBy3": "",
//                "cBy4": "",
//                "cBy5": "http://121.201.110.133:8089/cgi-bin/EmsData.dll?xLabel&2fcd29de29da12d754c742d72c5a284d2e5d2bef2cd621fb2da1281229565b"
//            }]
//        }
	}
}